#include "ptwrap.hpp"
#include <deque>
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <assert.h>

struct Message 
{
	Message(int mtype) : msgtype_(mtype)
	{ }
	virtual ~Message() { } // allow for polymorphism

	enum {
		EXIT,
		CANCEL,
		NORMAL, // first normal type
		SOME_MSG_1
	};
	int msgtype_;
	// ... whatever else is needed by the application ...
};

class SomeMessage : public Message
{
public:
	SomeMessage(int mtype) : Message(mtype)
	{ }
	virtual int getData()
	{
		return -1;
	}
	enum {
		URGENT_MSG_1 = NORMAL, // start after the base-class msg types
		URGENT_MSG_2,
		SOME_NORMAL,
		SOME_TYPE
	};
};

class Queue
{
public:
	Message *pop_front()
	{
		return 0;
	}
	void post(Message *m)
	{
	}
};

// [[ex04de]]
// DEBUG descr A writer thread may use a copy of the data after the message is posted.
class SomeHandler : public pw::pwthread
{

	void *execute()
	{
		while(true) {
			SomeMessage *m = (SomeMessage *)q_->pop_front();
			int mtype = m->msgtype_;
			switch (mtype) {
				// do some preparation depending on message type
			case SomeMessage::SOME_TYPE:
				// ... 
				break;
			}
			// ... now do some common processing ...
			nextq_->post(m);
			switch (mtype) {
				// do some clean-up depending on message type
			case SomeMessage::SOME_TYPE:
				// ... 
				break;
			}
		}
		return 0;
	}
	// DEBUG {
	Queue *q_, *nextq_;
	// DEBUG }
};
// END
